#pragma once

using namespace System::Collections::Generic;
using namespace System::Collections;
using namespace System::Runtime::InteropServices;

#include "CoVector.h"
#include "CoMatrix.h"
#include "CoCube.h"

#pragma unmanaged
#include <string>
#include <ql\time\date.hpp>
#include <ql\types.hpp>
#include <vector>
#pragma managed

#ifdef x64
		typedef __int64 Long;
		typedef unsigned __int64 ULong;
#else
		typedef long Long;
		typedef unsigned int ULong;
#endif

namespace Cephei
{
	public ref struct RangeException : public System::Exception { RangeException () : System::Exception() {}};
	public ref struct NullVectorException : public System::Exception { NullVectorException () : System::Exception() {}};

	public ref class ValueHelper
	{
	public:
		/////////////////////////////////////////////////////////////////////
		// Primitatives : overloaded methods provided simpler code-generation
		static System::Double Convert (double d)
		{
			return d;
		}
		static System::Int32 Convert (int d)
		{
			return d;
		}
#ifdef IS64BIT
		static System::Int64 Convert (long d)
		{
			return d;
		}
#else
		static long Convert (long d)
		{
			return (long)d;
		}
		static long Convert(__int64 d)
		{
			return (long)d;
		}
#endif
		static System::Boolean Convert (bool d)
		{
			return d;
		}

		static UInt64 Convert (UInt64 b)
		{
			return (UInt64)b;
		}
/*		static UInt64 Convert(unsigned __int64 d)
		{
			return (UInt64)d;
		}
*/
		static Int32 Convert (unsigned int i)
		{
			return (Int32)(int)i;
		}
		static double Convet (double* d)
		{
			return *d;
		}
		static double Convet (const double* d)
		{
			return *d;
		}
		/////////////////////////////////////////////////////////////////////
		// DateTime 
		static System::DateTime Convert (QuantLib::Date d)
		{
			System::DateTime dt (d.year(), d.month(), d.dayOfMonth());
			return dt;
		}

		static QuantLib::Date Convert (System::DateTime d)
		{
			QuantLib::Date qd (d.Day, (QuantLib::Month)d.Month, d.Year);
			return qd;
		}

		/////////////////////////////////////////////////////////////////////
		// String
		static System::String^ Convert (std::string s)
		{
			return gcnew System::String (s.c_str());
		}
		static std::string Convert (System::String^ s)
		{
			char* chars = (char*)(void*)Marshal::StringToHGlobalAnsi (s);
			std::string str (chars);
			Marshal::FreeHGlobal ((System::IntPtr)(void*)chars);
			return str;
		}
	};
	//////////////////////////////////////////////////////////////////////////////////////////////
	// implementation of Vector interface for basic/value types
	ref class CDoubleVector : public System::MarshalByRefObject,  
							    public INativeVector<double>,
								public INativeVector<Generic::ICell<double>^>
	{
	private:
		std::vector<double>* _pVValue;
		Object^ _owner;

	public:
		CDoubleVector ()
		{
			_pVValue = NULL;
		}
		CDoubleVector (std::vector<double>& rValue, Object^ owner)
		{
			_pVValue = &rValue;
			owner = _owner;
		}
		CDoubleVector (std::vector<double> rValue)
		{
			_pVValue = new std::vector<double> (rValue);
		}
		virtual ~CDoubleVector ()
		{
			if (_pVValue != NULL) delete _pVValue;
		}

		property int Count 
		{
			virtual int get ()
			{
				if (_pVValue != NULL) 
				{
					return _pVValue->size();
				}
				return 0;		// should never happen
			}
		}

		property double default[int] 
		{
			virtual double get (int index) = INativeVector<double>::default::get
			{
				if (_pVValue == NULL) throw gcnew NullVectorException ();
				if ((size_t)index >= _pVValue->size()) throw gcnew RangeException ();

				double native = (*_pVValue)[index];
				return native;
			}
			virtual void set (int index, double value) = INativeVector<double>::default::set
			{
				if (_pVValue != NULL)
				{
					if (_pVValue->size() <= (size_t)index)
					{
						// can't happen because vectors are filled from List<> sequentially
						if (_pVValue->size() < (size_t)index)
						{
							throw gcnew RangeException ();
						}
						_pVValue->push_back (value);
					}
					else
					{
						double& c = (*_pVValue)[index];
						c = value;
					}
				}
			}
		}

		//////////////////////////////////////////////////////////////////////////////////////////
		// Interface functions for cell vectors 
	public:
		property Generic::ICell<double>^ CItem[int] 
		{
			virtual Generic::ICell<double>^ get (int index) = INativeVector<Generic::ICell<double>^>::default::get
			{
				return CellBuilder::Instance->Create<double> (default[index]);
			}

			virtual void set (int index, Generic::ICell<double>^ value) = INativeVector<Generic::ICell<double>^>::default::set
			{
				default[index] = value->Value;
			}
		}
	public:
		std::vector<double>& GetReference ()
		{
			 return *_pVValue;
		}

		static operator std::vector<double>& (CDoubleVector^ a)
		{
			return a->GetReference();
		}
	public:
		virtual bool PrepareFeature (NativeFeature feature)
		{
			switch (feature)
			{
				case NativeFeature::Value :
					if (_pVValue == NULL)
					{
						_pVValue = new std::vector<double> ();
						return true;
					}
					break;
			}
			return false;
		}
	};
	ref class CDoubleMatrix : public System::MarshalByRefObject,  
								public INativeMatrix<double>,
								public INativeMatrix<Generic::ICell<double>^>
	{
	private:
		std::vector<std::vector<double>>* _pVValue;
		Object^ _owner;
	public:
		CDoubleMatrix ()
		{
			_pVValue = NULL;
		}
		CDoubleMatrix (std::vector<std::vector<double>>& rValue, Object^ owner)
		{
			_pVValue = &rValue;
			_owner = owner;
		}
		CDoubleMatrix (std::vector<std::vector<double>> rValue)
		{
			_pVValue = new std::vector<std::vector<double>> (rValue);
		}
		virtual ~CDoubleMatrix ()
		{
			if (_pVValue != NULL) delete _pVValue;
		}

		property int Count 
		{
			virtual int get ()
			{
				if (_pVValue != NULL) 
				{
					return _pVValue->size();
				}
				return 0;		// should never happen
			}
		}

		property double default[int, int] 
		{
			virtual double get (int x, int y) = INativeMatrix<double>::default::get
			{
				if (_pVValue == NULL) throw gcnew NullVectorException ();
				if ((size_t)x >= _pVValue->size() || (size_t)y >= (*_pVValue)[x].size()) throw gcnew RangeException ();

				double& native = (*_pVValue)[x][y];
				return native;
			}
			virtual void set (int x, int y, double value) = INativeMatrix<double>::default::set
			{
				if (_pVValue != NULL)
				{
					if (_pVValue->size() <= (size_t)x)
					{
						// can't happen because vectors are filled from List<> sequentially
						if (_pVValue->size()-1 < (size_t)x) throw gcnew RangeException ();

						_pVValue->push_back (std::vector<double>());
					}
					if ((*_pVValue)[x].size() <= (size_t)y)
					{
						if ((*_pVValue)[x].size() < (size_t)y) throw gcnew RangeException ();

						(*_pVValue)[x].push_back (value);
					}
					double& c = (*_pVValue)[x][y];
					c = value;
				}
			}
		}

		property Generic::ICell<double>^ CItem[int, int] 
		{
			virtual Generic::ICell<double>^ get (int x, int y) = INativeMatrix<Generic::ICell<double>^>::default::get
			{
				return CellBuilder::Instance->Create<double> (default[x,y]);
			}
			virtual void set (int x, int y, Generic::ICell<double>^ value) = INativeMatrix<Generic::ICell<double>^>::default::set
			{
				default[x,y] = value->Value;
			}
		}

	public:
		std::vector<std::vector<double>>& GetReference ()
		{
			 return *_pVValue;
		}

		static operator std::vector<std::vector<double>>& (CDoubleMatrix^ a)
		{
			return a->GetReference();
		}
	public:
		virtual bool PrepareFeature (NativeFeature feature)
		{
			switch (feature)
			{
				case NativeFeature::Value :
					if (_pVValue == NULL)
					{
						_pVValue = new std::vector<std::vector<double>> ();
						return true;
					}
					break;
			}
			return false;
		}
	public:
		virtual INativeVector<double>^ CreateVector () = INativeMatrix<double>::CreateVector
		{
			return gcnew CDoubleVector ();
		}
	public:
		virtual INativeVector<Generic::ICell<double>^>^ CreateCellVector () = INativeMatrix<Generic::ICell<double>^>::CreateVector
		{
			return gcnew CDoubleVector ();
		}
	};

	ref class CDoubleCube : public System::MarshalByRefObject,  
							  public INativeCube<double>,
							  public INativeCube<Generic::ICell<double>^>
	{
	private:
		std::vector<std::vector<std::vector<double>>>* _pVValue;
		Object^ _owner;
	public:
		CDoubleCube ()
		{
			_pVValue = NULL;
		}
		CDoubleCube (std::vector<std::vector<std::vector<double>>>& rValue, Object^ owner)
		{
			_pVValue = &rValue;
			_owner = owner;
		}
		CDoubleCube (std::vector<std::vector<std::vector<double>>> rValue)
		{
			_pVValue = new std::vector<std::vector<std::vector<double>>> (rValue);
		}
		virtual ~CDoubleCube ()
		{
			if (_pVValue != NULL) delete _pVValue;
		}
		property int Count 
		{
			virtual int get ()
			{
				if (_pVValue != NULL) 
				{
					return _pVValue->size();
				}
				return 0;		// should never happen
			}
		}

		property double default[int, int, int] 
		{
			virtual double get (int x, int y, int z) = INativeCube<double>::default::get
			{
				if (_pVValue == NULL) throw gcnew NullVectorException ();
				if ((size_t)x >= _pVValue->size() || (size_t)y >= (*_pVValue)[x].size() || (size_t)z >= (*_pVValue)[x][y].size()) throw gcnew RangeException ();

				double& native = (*_pVValue)[x][y][z];
				return native;
			}
			virtual void set (int x, int y, int z, double value) = INativeCube<double>::default::set
			{
				if (_pVValue != NULL)
				{
					if (_pVValue->size() <= (size_t)x)
					{
						// can't happen because vectors are filled from List<> sequentially
						if (_pVValue->size()-1 < (size_t)x) throw gcnew RangeException ();

						_pVValue->push_back (std::vector<std::vector<double>>());
					}
					if ((*_pVValue)[x].size() <= (size_t)y)
					{
						if ((*_pVValue)[x].size() < (size_t)y) throw gcnew RangeException ();

						(*_pVValue)[x].push_back (std::vector<double> ());
					}
					if ((*_pVValue)[x][y].size() <= (size_t)z)
					{
						if ((*_pVValue)[x][y].size() < (size_t)z) throw gcnew RangeException ();

						(*_pVValue)[x][y].push_back (value);
					}
					double& c = (*_pVValue)[x][y][z];
					c = value;
				}
			}
		}

		property Generic::ICell<double>^ CItem[int, int, int] 
		{
			virtual Generic::ICell<double>^ get (int x, int y, int z) = INativeCube<Generic::ICell<double>^>::default::get
			{
				return CellBuilder::Instance->Create<double> (default[x,y,z]);
			}
			virtual void set (int x, int y, int z, Generic::ICell<double>^ value) = INativeCube<Generic::ICell<double>^>::default::set
			{
				default[x,y,z] = value->Value;
			}
		}

	public:
		std::vector<std::vector<std::vector<double>>>& GetReference ()
		{
			 return *_pVValue;
		}

	public:
		virtual bool PrepareFeature (NativeFeature feature)
		{
			switch (feature)
			{
				case NativeFeature::Value :
					if (_pVValue == NULL)
					{
						_pVValue = new std::vector<std::vector<std::vector<double>>> ();
						return true;
					}
					break;
			}
			return false;
		}
	public:
		virtual INativeMatrix<double>^ CreateMatrix () = INativeCube<double>::CreateMatrix
		{
			return gcnew CDoubleMatrix ();
		}
	public:
		virtual INativeMatrix<Generic::ICell<double>^>^ CreateCellMatrix () = INativeCube<Generic::ICell<double>^>::CreateMatrix
		{
			return gcnew CDoubleMatrix ();
		}
	};

	ref class CIntVector : public System::MarshalByRefObject,  
							    public INativeVector<int>,
							    public INativeVector<Generic::ICell<int>^>
	{
	private:
		std::vector<int>* _pVValue;

	public:
		CIntVector ()
		{
			_pVValue = NULL;
		}
		CIntVector (std::vector<int>& rValue)
		{
			_pVValue = &rValue;
		}
		CIntVector (std::vector<int> rValue)
		{
			_pVValue = new std::vector<int> (rValue);
		}
		virtual ~CIntVector ()
		{
			if (_pVValue != NULL) delete _pVValue;
		}

		property int Count 
		{
			virtual int get ()
			{
				if (_pVValue != NULL) 
				{
					return _pVValue->size();
				}
				return 0;		// should never happen
			}
		}

		property int default[int] 
		{
			virtual int get (int index) = INativeVector<int>::default::get
			{
				if (_pVValue == NULL) throw gcnew NullVectorException ();
				if ((size_t)index >= _pVValue->size()) throw gcnew RangeException ();

				int native = (*_pVValue)[index];
				return native;
			}
			virtual void set (int index, int value) = INativeVector<int>::default::set
			{
				if (_pVValue != NULL)
				{
					if (_pVValue->size() <= (size_t)index)
					{
						// can't happen because vectors are filled from List<> sequentially
						if (_pVValue->size() < (size_t)index)
						{
							throw gcnew RangeException ();
						}
						_pVValue->push_back (value);
					}
					else
					{
						int& c = (*_pVValue)[index];
						c = value;
					}
				}
			}
		}

		//////////////////////////////////////////////////////////////////////////////////////////
		// Interface functions for cell vectors 
	public:
		property Generic::ICell<int>^ CItem[int] 
		{
			virtual Generic::ICell<int>^ get (int index) = INativeVector<Generic::ICell<int>^>::default::get
			{
				return CellBuilder::Instance->Create<int> (default[index]);
			}

			virtual void set (int index, Generic::ICell<int>^ value) = INativeVector<Generic::ICell<int>^>::default::set
			{
				default[index] = value->Value;
			}
		}
	public:
		std::vector<int>& GetReference ()
		{
			 return *_pVValue;
		}

	public:
		virtual bool PrepareFeature (NativeFeature feature)
		{
			switch (feature)
			{
				case NativeFeature::Value :
					if (_pVValue == NULL)
					{
						_pVValue = new std::vector<int> ();
						return true;
					}
					break;
			}
			return false;
		}
	};
	ref class CIntMatrix : public System::MarshalByRefObject,  
								public INativeMatrix<int>,
							    public INativeMatrix<Generic::ICell<int>^>
	{
	private:
		std::vector<std::vector<int>>* _pVValue;
		Object^ _owner;
	public:
		CIntMatrix ()
		{
			_pVValue = NULL;
		}
		CIntMatrix (std::vector<std::vector<int>>& rValue, Object^ owner)
		{
			_pVValue = &rValue;
			_owner = owner;
		}
		CIntMatrix (std::vector<std::vector<int>> rValue)
		{
			_pVValue = new std::vector<std::vector<int>> (rValue);
		}
		virtual ~CIntMatrix ()
		{
			if (_pVValue != NULL) delete _pVValue;
		}
		property int Count 
		{
			virtual int get ()
			{
				if (_pVValue != NULL) 
				{
					return _pVValue->size();
				}
				return 0;		// should never happen
			}
		}
		property int default[int, int] 
		{
			virtual int get (int x, int y) = INativeMatrix<int>::default::get
			{
				if (_pVValue == NULL) throw gcnew NullVectorException ();
				if ((size_t)x >= _pVValue->size() || (size_t)y >= (*_pVValue)[x].size()) throw gcnew RangeException ();

				int& native = (*_pVValue)[x][y];
				return native;
			}
			virtual void set (int x, int y, int value) = INativeMatrix<int>::default::set
			{
				if (_pVValue != NULL)
				{
					if (_pVValue->size() <= (size_t)x)
					{
						// can't happen because vectors are filled from List<> sequentially
						if (_pVValue->size()-1 < (size_t)x) throw gcnew RangeException ();

						_pVValue->push_back (std::vector<int>());
					}
					if ((*_pVValue)[x].size() <= (size_t)y)
					{
						if ((*_pVValue)[x].size() < (size_t)y) throw gcnew RangeException ();

						(*_pVValue)[x].push_back (value);
					}
					int& c = (*_pVValue)[x][y];
					c = value;
				}
			}
		}

		property Generic::ICell<int>^ CItem[int, int] 
		{
			virtual Generic::ICell<int>^ get (int x, int y) = INativeMatrix<Generic::ICell<int>^>::default::get
			{
				return CellBuilder::Instance->Create<int> (default[x,y]);
			}
			virtual void set (int x, int y, Generic::ICell<int>^ value) = INativeMatrix<Generic::ICell<int>^>::default::set
			{
				default[x,y] = value->Value;
			}
		}

	public:
		std::vector<std::vector<int>>& GetReference ()
		{
			 return *_pVValue;
		}

	public:
		virtual bool PrepareFeature (NativeFeature feature)
		{
			switch (feature)
			{
				case NativeFeature::Value :
					if (_pVValue == NULL)
					{
						_pVValue = new std::vector<std::vector<int>> ();
						return true;
					}
					break;
			}
			return false;
		}
	public:
		virtual INativeVector<int>^ CreateVector () = INativeMatrix<int>::CreateVector
		{
			return gcnew CIntVector ();
		}
	public:
		virtual INativeVector<Generic::ICell<int>^>^ CreateCellVector () = INativeMatrix<Generic::ICell<int>^>::CreateVector
		{
			return gcnew CIntVector ();
		}
	};

	ref class CIntCube : public System::MarshalByRefObject,  
							  public INativeCube<int>,
							  public INativeCube<Generic::ICell<int>^>
	{
	private:
		std::vector<std::vector<std::vector<int>>>* _pVValue;
		Object^ _owner;
	public:
		CIntCube ()
		{
			_pVValue = NULL;
		}
		CIntCube (std::vector<std::vector<std::vector<int>>>& rValue, Object^ owner)
		{
			_pVValue = &rValue;
			_owner = owner;
		}
		CIntCube (std::vector<std::vector<std::vector<int>>> rValue)
		{
			_pVValue = new std::vector<std::vector<std::vector<int>>> (rValue);
		}
		virtual ~CIntCube ()
		{
			if (_pVValue != NULL) delete _pVValue;
		}
		property int Count 
		{
			virtual int get ()
			{
				if (_pVValue != NULL) 
				{
					return _pVValue->size();
				}
				return 0;		// should never happen
			}
		}

		property int default[int, int, int] 
		{
			virtual int get (int x, int y, int z) = INativeCube<int>::default::get
			{
				if (_pVValue == NULL) throw gcnew NullVectorException ();
				if ((size_t)x >= _pVValue->size() || (size_t)y >= (*_pVValue)[x].size() || (size_t)z >= (*_pVValue)[x][y].size()) throw gcnew RangeException ();

				int& native = (*_pVValue)[x][y][z];
				return native;
			}
			virtual void set (int x, int y, int z, int value) = INativeCube<int>::default::set
			{
				if (_pVValue != NULL)
				{
					if (_pVValue->size() <= (size_t)x)
					{
						// can't happen because vectors are filled from List<> sequentially
						if (_pVValue->size()-1 < (size_t)x) throw gcnew RangeException ();

						_pVValue->push_back (std::vector<std::vector<int>>());
					}
					if ((*_pVValue)[x].size() <= (size_t)y)
					{
						if ((*_pVValue)[x].size() < (size_t)y) throw gcnew RangeException ();

						(*_pVValue)[x].push_back (std::vector<int> ());
					}
					if ((*_pVValue)[x][y].size() <= (size_t)z)
					{
						if ((*_pVValue)[x][y].size() < (size_t)z) throw gcnew RangeException ();

						(*_pVValue)[x][y].push_back (value);
					}
					int& c = (*_pVValue)[x][y][z];
					c = value;
				}
			}
		}

		property Generic::ICell<int>^ CItem[int, int, int] 
		{
			virtual Generic::ICell<int>^ get (int x, int y, int z) = INativeCube<Generic::ICell<int>^>::default::get
			{
				return CellBuilder::Instance->Create<int> (default[x,y,z]);
			}
			virtual void set (int x, int y, int z, Generic::ICell<int>^ value) = INativeCube<Generic::ICell<int>^>::default::set
			{
				default[x,y,z] = value->Value;
			}
		}

	public:
		std::vector<std::vector<std::vector<int>>>& GetReference ()
		{
			 return *_pVValue;
		}

	public:
		virtual bool PrepareFeature (NativeFeature feature)
		{
			switch (feature)
			{
				case NativeFeature::Value :
					if (_pVValue == NULL)
					{
						_pVValue = new std::vector<std::vector<std::vector<int>>> ();
						return true;
					}
					break;
			}
			return false;
		}
	public:
		virtual INativeMatrix<int>^ CreateMatrix () = INativeCube<int>::CreateMatrix
		{
			return gcnew CIntMatrix ();
		}
	public:
		virtual INativeMatrix<Generic::ICell<int>^>^ CreateCellMatrix () = INativeCube<Generic::ICell<int>^>::CreateMatrix
		{
			return gcnew CIntMatrix ();
		}
	};
	typedef CIntVector CInt32Vector;
	typedef CIntMatrix CInt32Matrix;
	typedef CIntCube CInt32Cube;

	ref class CUIntVector : public System::MarshalByRefObject,  
							    public INativeVector<UInt32>,
							    public INativeVector<Generic::ICell<UInt32>^>
	{
	private:
		std::vector<unsigned int>* _pVValue;
		Object^ _owner;

	public:
		CUIntVector ()
		{
			_pVValue = NULL;
		}
		CUIntVector (std::vector<unsigned int>& rValue, Object^ owner)
		{
			_pVValue = &rValue;
			_owner = owner;
		}
		CUIntVector (std::vector<unsigned int> rValue)
		{
			_pVValue = new std::vector<unsigned int> (rValue);
		}
		virtual ~CUIntVector ()
		{
			if (_pVValue != NULL) delete _pVValue;
		}

		property int Count 
		{
			virtual int get ()
			{
				if (_pVValue != NULL) 
				{
					return _pVValue->size();
				}
				return 0;		// should never happen
			}
		}

		property UInt32 default[int] 
		{
			virtual UInt32 get (int index) = INativeVector<UInt32>::default::get
			{
				if (_pVValue == NULL) throw gcnew NullVectorException ();
				if ((size_t)index >= _pVValue->size()) throw gcnew RangeException ();

				UInt32 native = (*_pVValue)[index];
				return native;
			}
			virtual void set (int index, UInt32 value) = INativeVector<UInt32>::default::set
			{
				if (_pVValue != NULL)
				{
					if (_pVValue->size() <= (size_t)index)
					{
						// can't happen because vectors are filled from List<> sequentially
						if (_pVValue->size() < (size_t)index)
						{
							throw gcnew RangeException ();
						}
						_pVValue->push_back (value);
					}
					else
					{
						UInt32& c = (*_pVValue)[index];
						c = value;
					}
				}
			}
		}

		//////////////////////////////////////////////////////////////////////////////////////////
		// UInterface functions for cell vectors 
	public:
		property Generic::ICell<UInt32>^ CItem[int] 
		{
			virtual Generic::ICell<UInt32>^ get (int index) = INativeVector<Generic::ICell<UInt32>^>::default::get
			{
				return CellBuilder::Instance->Create<UInt32> (default[index]);
			}

			virtual void set (int index, Generic::ICell<UInt32>^ value) = INativeVector<Generic::ICell<UInt32>^>::default::set
			{
				default[index] = value->Value;
			}
		}
	public:
		std::vector<unsigned int>& GetReference ()
		{
			 return *_pVValue;
		}

		static operator std::vector<unsigned int>& (CUIntVector^ a)
		{
			return a->GetReference();
		}
	public:
		virtual bool PrepareFeature (NativeFeature feature)
		{
			switch (feature)
			{
				case NativeFeature::Value :
					if (_pVValue == NULL)
					{
						_pVValue = new std::vector<unsigned int> ();
						return true;
					}
					break;
			}
			return false;
		}
	};
	ref class CUIntMatrix : public System::MarshalByRefObject,  
								public INativeMatrix<UInt32>,
							    public INativeMatrix<Generic::ICell<UInt32>^>
	{
	private:
		std::vector<std::vector<unsigned int>>* _pVValue;
		Object^ _owner;
	public:
		CUIntMatrix ()
		{
			_pVValue = NULL;
		}
		CUIntMatrix (std::vector<std::vector<unsigned int>>& rValue, Object^ owner)
		{
			_pVValue = &rValue;
			_owner = owner;
		}
		CUIntMatrix (std::vector<std::vector<unsigned int>> rValue)
		{
			_pVValue = new std::vector<std::vector<unsigned int>> (rValue);
		}
		virtual ~CUIntMatrix ()
		{
			if (_pVValue != NULL) delete _pVValue;
		}
		property int Count 
		{
			virtual int get ()
			{
				if (_pVValue != NULL) 
				{
					return _pVValue->size();
				}
				return 0;		// should never happen
			}
		}

		property UInt32 default[int, int] 
		{
			virtual UInt32 get (int x, int y) = INativeMatrix<UInt32>::default::get
			{
				if (_pVValue == NULL) throw gcnew NullVectorException ();
				if ((size_t)x >= _pVValue->size() || (size_t)y >= (*_pVValue)[x].size()) throw gcnew RangeException ();

				UInt32& native = (*_pVValue)[x][y];
				return native;
			}
			virtual void set (int x, int y, UInt32 value) = INativeMatrix<UInt32>::default::set
			{
				if (_pVValue != NULL)
				{
					if (_pVValue->size() <= (size_t)x)
					{
						// can't happen because vectors are filled from List<> sequentially
						if (_pVValue->size()-1 < (size_t)x) throw gcnew RangeException ();

						_pVValue->push_back (std::vector<UInt32>());
					}
					if ((*_pVValue)[x].size() <= (size_t)y)
					{
						if ((*_pVValue)[x].size() < (size_t)y) throw gcnew RangeException ();

						(*_pVValue)[x].push_back (value);
					}
					UInt32& c = (*_pVValue)[x][y];
					c = value;
				}
			}
		}

		property Generic::ICell<UInt32>^ CItem[int, int] 
		{
			virtual Generic::ICell<UInt32>^ get (int x, int y) = INativeMatrix<Generic::ICell<UInt32>^>::default::get
			{
				return CellBuilder::Instance->Create<UInt32> (default[x,y]);
			}
			virtual void set (int x, int y, Generic::ICell<UInt32>^ value) = INativeMatrix<Generic::ICell<UInt32>^>::default::set
			{
				default[x,y] = value->Value;
			}
		}

	public:
		std::vector<std::vector<unsigned int>>& GetReference ()
		{
			 return *_pVValue;
		}

		static operator std::vector<std::vector<unsigned int>>& (CUIntMatrix^ a)
		{
			return a->GetReference();
		}
	public:
		virtual bool PrepareFeature (NativeFeature feature)
		{
			switch (feature)
			{
				case NativeFeature::Value :
					if (_pVValue == NULL)
					{
						_pVValue = new std::vector<std::vector<unsigned int>> ();
						return true;
					}
					break;
			}
			return false;
		}
	public:
		virtual INativeVector<UInt32>^ CreateVector () = INativeMatrix<UInt32>::CreateVector
		{
			return gcnew CUIntVector ();
		}
	public:
		virtual INativeVector<Generic::ICell<UInt32>^>^ CreateCellVector () = INativeMatrix<Generic::ICell<UInt32>^>::CreateVector
		{
			return gcnew CUIntVector ();
		}
	};

	ref class CUIntCube : public System::MarshalByRefObject,  
							  public INativeCube<UInt32>,
							  public INativeCube<Generic::ICell<UInt32>^>
	{
	private:
		std::vector<std::vector<std::vector<UInt32>>>* _pVValue;
		Object^ _owner;
	public:
		CUIntCube ()
		{
			_pVValue = NULL;
		}
		CUIntCube (std::vector<std::vector<std::vector<unsigned int>>>& rValue, Object^ owner)
		{
			_pVValue = &rValue;
			_owner = owner;
		}
		CUIntCube (std::vector<std::vector<std::vector<unsigned int>>> rValue)
		{
			_pVValue = new std::vector<std::vector<std::vector<unsigned int>>> (rValue);
		}
		virtual ~CUIntCube ()
		{
			if (_pVValue != NULL) delete _pVValue;
		}
		property int Count 
		{
			virtual int get ()
			{
				if (_pVValue != NULL) 
				{
					return _pVValue->size();
				}
				return 0;		// should never happen
			}
		}

		property UInt32 default[int, int, int] 
		{
			virtual UInt32 get (int x, int y, int z) = INativeCube<UInt32>::default::get
			{
				if (_pVValue == NULL) throw gcnew NullVectorException ();
				if ((size_t)x >= _pVValue->size() || (size_t)y >= (*_pVValue)[x].size() || (size_t)z >= (*_pVValue)[x][y].size()) throw gcnew RangeException ();

				UInt32& native = (*_pVValue)[x][y][z];
				return native;
			}
			virtual void set (int x, int y, int z, UInt32 value) = INativeCube<UInt32>::default::set
			{
				if (_pVValue != NULL)
				{
					if (_pVValue->size() <= (size_t)x)
					{
						// can't happen because vectors are filled from List<> sequentially
						if (_pVValue->size()-1 < (size_t)x) throw gcnew RangeException ();

						_pVValue->push_back (std::vector<std::vector<UInt32>>());
					}
					if ((*_pVValue)[x].size() <= (size_t)y)
					{
						if ((*_pVValue)[x].size() < (size_t)y) throw gcnew RangeException ();

						(*_pVValue)[x].push_back (std::vector<UInt32> ());
					}
					if ((*_pVValue)[x][y].size() <= (size_t)z)
					{
						if ((*_pVValue)[x][y].size() < (size_t)z) throw gcnew RangeException ();

						(*_pVValue)[x][y].push_back (value);
					}
					UInt32& c = (*_pVValue)[x][y][z];
					c = value;
				}
			}
		}

		property Generic::ICell<UInt32>^ CItem[int, int, int] 
		{
			virtual Generic::ICell<UInt32>^ get (int x, int y, int z) = INativeCube<Generic::ICell<UInt32>^>::default::get
			{
				return CellBuilder::Instance->Create<UInt32> (default[x,y,z]);
			}
			virtual void set (int x, int y, int z, Generic::ICell<UInt32>^ value) = INativeCube<Generic::ICell<UInt32>^>::default::set
			{
				default[x,y,z] = value->Value;
			}
		}

	public:
		std::vector<std::vector<std::vector<unsigned int>>>& GetReference ()
		{
			 return *_pVValue;
		}

		static operator std::vector<std::vector<std::vector<unsigned int>>>& (CUIntCube^ a)
		{
			return a->GetReference();
		}
	public:
		virtual bool PrepareFeature (NativeFeature feature)
		{
			switch (feature)
			{
				case NativeFeature::Value :
					if (_pVValue == NULL)
					{
						_pVValue = new std::vector<std::vector<std::vector<unsigned int>>> ();
						return true;
					}
					break;
			}
			return false;
		}
	public:
		virtual INativeMatrix<UInt32>^ CreateMatrix () = INativeCube<UInt32>::CreateMatrix
		{
			return gcnew CUIntMatrix ();
		}
	public:
		virtual INativeMatrix<Generic::ICell<UInt32>^>^ CreateCellMatrix () = INativeCube<Generic::ICell<UInt32>^>::CreateMatrix
		{
			return gcnew CUIntMatrix ();
		}
	};

	typedef CUIntVector CUInt32Vector;
	typedef CUIntMatrix CUInt32Matrix;
	typedef CUIntCube CUInt32Cube;

	ref class CLongVector : public System::MarshalByRefObject,  
							    public INativeVector<Int64>,
							    public INativeVector<Generic::ICell<Int64>^>
	{
	private:
		std::vector<Long>* _pVValue;
		Object^ _owner;
	public:
		CLongVector ()
		{
			_pVValue = NULL;
		}
		CLongVector (std::vector<Long>& rValue, Object^ owner)
		{
			_pVValue = &rValue;
			_owner = owner;
		}
		CLongVector (std::vector<Long> rValue)
		{
			_pVValue = new std::vector<Long> (rValue);
		}
		virtual ~CLongVector ()
		{
			if (_pVValue != NULL) delete _pVValue;
		}

		property int Count 
		{
			virtual int get ()
			{
				if (_pVValue != NULL) 
				{
					return _pVValue->size();
				}
				return 0;		// should never happen
			}
		}

		property Int64 default[int] 
		{
			virtual Int64 get (int index) = INativeVector<Int64>::default::get
			{
				if (_pVValue == NULL) throw gcnew NullVectorException ();
				if ((size_t)index >= _pVValue->size()) throw gcnew RangeException ();

				Int64 native = (*_pVValue)[index];
				return native;
			}
			virtual void set (int index, Int64 value) = INativeVector<Int64>::default::set
			{
				if (_pVValue != NULL)
				{
					if (_pVValue->size() <= (size_t)index)
					{
						// can't happen because vectors are filled from List<> sequentially
						if (_pVValue->size() < (size_t)index)
						{
							throw gcnew RangeException ();
						}
						_pVValue->push_back ((Long)value);
					}
					else
					{
						Long& c = (*_pVValue)[index];
						c = (Long)value;
					}
				}
			}
		}


		//////////////////////////////////////////////////////////////////////////////////////////
		// Interface functions for cell vectors 
	public:
		property Generic::ICell<Int64>^ CItem[int] 
		{
			virtual Generic::ICell<Int64>^ get (int index) = INativeVector<Generic::ICell<Int64>^>::default::get
			{
				return CellBuilder::Instance->Create<Int64> (default[index]);
			}

			virtual void set (int index, Generic::ICell<Int64>^ value) = INativeVector<Generic::ICell<Int64>^>::default::set
			{
				default[index] = value->Value;
			}
		}
	public:
		std::vector<Long>& GetReference ()
		{
			 return *_pVValue;
		}

		static operator std::vector<Long>& (CLongVector^ a)
		{
			return a->GetReference();
		}
	public:
		virtual bool PrepareFeature (NativeFeature feature)
		{
			switch (feature)
			{
				case NativeFeature::Value :
					if (_pVValue == NULL)
					{
						_pVValue = new std::vector<Long> ();
						return true;
					}
					break;
			}
			return false;
		}
	};
	ref class CLongMatrix : public System::MarshalByRefObject,  
								public INativeMatrix<Int64>,
							    public INativeMatrix<Generic::ICell<Int64>^>
	{
	private:
		std::vector<std::vector<Long>>* _pVValue;
		Object^ _owner;
	public:
		CLongMatrix ()
		{
			_pVValue = NULL;
		}
		CLongMatrix (std::vector<std::vector<Long>>& rValue, Object^ owner)
		{
			_pVValue = &rValue;
			_owner = owner;
		}
		CLongMatrix (std::vector<std::vector<Long>> rValue)
		{
			_pVValue = new std::vector<std::vector<Long>> (rValue);
		}
		virtual ~CLongMatrix ()
		{
			if (_pVValue != NULL) delete _pVValue;
		}
		property int Count 
		{
			virtual int get ()
			{
				if (_pVValue != NULL) 
				{
					return _pVValue->size();
				}
				return 0;		// should never happen
			}
		}

		property Int64 default[int, int] 
		{
			virtual Int64 get (int x, int y) = INativeMatrix<Int64>::default::get
			{
				if (_pVValue == NULL) throw gcnew NullVectorException ();
				if ((size_t)x >= _pVValue->size() || (size_t)y >= (*_pVValue)[x].size()) throw gcnew RangeException ();

				Long& native = (*_pVValue)[x][y];
				return (Int64)native;
			}
			virtual void set (int x, int y, Int64 value) = INativeMatrix<Int64>::default::set
			{
				if (_pVValue != NULL)
				{
					if (_pVValue->size() <= (size_t)x)
					{
						// can't happen because vectors are filled from List<> sequentially
						if (_pVValue->size()-1 < (size_t)x) throw gcnew RangeException ();

						_pVValue->push_back (std::vector<Long>());
					}
					if ((*_pVValue)[x].size() <= (size_t)y)
					{
						if ((*_pVValue)[x].size() < (size_t)y) throw gcnew RangeException ();

						(*_pVValue)[x].push_back ((Long)value);
					}
					Long& c = (*_pVValue)[x][y];
					c = (Long)value;
				}
			}
		}

		property Generic::ICell<Int64>^ CItem[int, int] 
		{
			virtual Generic::ICell<Int64>^ get (int x, int y) = INativeMatrix<Generic::ICell<Int64>^>::default::get
			{
				return CellBuilder::Instance->Create<Int64> (default[x,y]);
			}
			virtual void set (int x, int y, Generic::ICell<Int64>^ value) = INativeMatrix<Generic::ICell<Int64>^>::default::set
			{
				default[x,y] = value->Value;
			}
		}

	public:
		std::vector<std::vector<Long>>& GetReference ()
		{
			 return *_pVValue;
		}

		static operator std::vector<std::vector<Long>>& (CLongMatrix^ a)
		{
			return a->GetReference();
		}
	public:
		virtual bool PrepareFeature (NativeFeature feature)
		{
			switch (feature)
			{
				case NativeFeature::Value :
					if (_pVValue == NULL)
					{
						_pVValue = new std::vector<std::vector<Long>> ();
						return true;
					}
					break;
			}
			return false;
		}
	public:
		virtual INativeVector<Int64>^ CreateVector () = INativeMatrix<Int64>::CreateVector
		{
			return gcnew CLongVector ();
		}
	public:
		virtual INativeVector<Generic::ICell<Int64>^>^ CreateCellVector () = INativeMatrix<Generic::ICell<Int64>^>::CreateVector
		{
			return gcnew CLongVector ();
		}
	};

	ref class CLongCube : public System::MarshalByRefObject,  
							  public INativeCube<Int64>,
							  public INativeCube<Generic::ICell<Int64>^>
	{
	private:
		std::vector<std::vector<std::vector<Long>>>* _pVValue;
		Object^ _owner;
	public:
		CLongCube ()
		{
			_pVValue = NULL;
		}
		CLongCube (std::vector<std::vector<std::vector<Long>>>& rValue, Object^ owner)
		{
			_pVValue = &rValue;
			_owner = owner;
		}
		CLongCube (std::vector<std::vector<std::vector<Long>>> rValue)
		{
			_pVValue = new std::vector<std::vector<std::vector<Long>>> (rValue);
		}
		virtual ~CLongCube ()
		{
			if (_pVValue != NULL) delete _pVValue;
		}
		property int Count 
		{
			virtual int get ()
			{
				if (_pVValue != NULL) 
				{
					return _pVValue->size();
				}
				return 0;		// should never happen
			}
		}

		property Int64 default[int, int, int] 
		{
			virtual Int64 get (int x, int y, int z) = INativeCube<Int64>::default::get
			{
				if (_pVValue == NULL) throw gcnew NullVectorException ();
				if ((size_t)x >= _pVValue->size() || (size_t)y >= (*_pVValue)[x].size() || (size_t)z >= (*_pVValue)[x][y].size()) throw gcnew RangeException ();

				Long& native = (*_pVValue)[x][y][z];
				return (Int64)native;
			}
			virtual void set (int x, int y, int z, Int64 value) = INativeCube<Int64>::default::set
			{
				if (_pVValue != NULL)
				{
					if (_pVValue->size() <= (size_t)x)
					{
						// can't happen because vectors are filled from List<> sequentially
						if (_pVValue->size()-1 < (size_t)x) throw gcnew RangeException ();

						_pVValue->push_back (std::vector<std::vector<Long>>());
					}
					if ((*_pVValue)[x].size() <= (size_t)y)
					{
						if ((*_pVValue)[x].size() < (size_t)y) throw gcnew RangeException ();

						(*_pVValue)[x].push_back (std::vector<Long> ());
					}
					if ((*_pVValue)[x][y].size() <= (size_t)z)
					{
						if ((*_pVValue)[x][y].size() < (size_t)z) throw gcnew RangeException ();

						(*_pVValue)[x][y].push_back ((Long)value);
					}
					Long& c = (*_pVValue)[x][y][z];
					c = (Long)value;
				}
			}
		}

		property Generic::ICell<Int64>^ CItem[int, int, int] 
		{
			virtual Generic::ICell<Int64>^ get (int x, int y, int z) = INativeCube<Generic::ICell<Int64>^>::default::get
			{
				return CellBuilder::Instance->Create<Int64> (default[x,y,z]);
			}
			virtual void set (int x, int y, int z, Generic::ICell<Int64>^ value) = INativeCube<Generic::ICell<Int64>^>::default::set
			{
				default[x,y,z] = value->Value;
			}
		}

	public:
		std::vector<std::vector<std::vector<Long>>>& GetReference ()
		{
			 return *_pVValue;
		}

		static operator std::vector<std::vector<std::vector<Long>>>& (CLongCube^ a)
		{
			return a->GetReference();
		}
	public:
		virtual bool PrepareFeature (NativeFeature feature)
		{
			switch (feature)
			{
				case NativeFeature::Value :
					if (_pVValue == NULL)
					{
						_pVValue = new std::vector<std::vector<std::vector<Long>>> ();
						return true;
					}
					break;
			}
			return false;
		}
	public:
		virtual INativeMatrix<Int64>^ CreateMatrix () = INativeCube<Int64>::CreateMatrix
		{
			return gcnew CLongMatrix ();
		}
	public:
		virtual INativeMatrix<Generic::ICell<Int64>^>^ CreateCellMatrix () = INativeCube<Generic::ICell<Int64>^>::CreateMatrix
		{
			return gcnew CLongMatrix ();
		}
	};
	typedef CLongVector CInt64Vector;
	typedef CLongMatrix CInt64Matrix;
	typedef CLongCube CInt64Cube;
	ref class CULongVector : public System::MarshalByRefObject,  
							    public INativeVector<UInt64>,
							    public INativeVector<Generic::ICell<UInt64>^>
	{
	private:
		std::vector<ULong>* _pVValue;
		Object^ _owner;
	public:
		CULongVector ()
		{
			_pVValue = NULL;
		}
		CULongVector (std::vector<ULong>& rValue, Object^ owner)
		{
			_pVValue = &rValue;
			_owner = owner;
		}
		CULongVector (std::vector<ULong> rValue)
		{
			_pVValue = new std::vector<ULong> (rValue);
		}
		virtual ~CULongVector ()
		{
			if (_pVValue != NULL) delete _pVValue;
		}

		property int Count 
		{
			virtual int get ()
			{
				if (_pVValue != NULL) 
				{
					return _pVValue->size();
				}
				return 0;		// should never happen
			}
		}

		property UInt64 default[int] 
		{
			virtual UInt64 get (int index) = INativeVector<UInt64>::default::get
			{
				if (_pVValue == NULL) throw gcnew NullVectorException ();
				if ((size_t)index >= _pVValue->size()) throw gcnew RangeException ();

				UInt64 native = (*_pVValue)[index];
				return native;
			}
			virtual void set (int index, UInt64 value) = INativeVector<UInt64>::default::set
			{
				if (_pVValue != NULL)
				{
					if (_pVValue->size() <= (size_t)index)
					{
						// can't happen because vectors are filled from List<> sequentially
						if (_pVValue->size() < (size_t)index)
						{
							throw gcnew RangeException ();
						}
						_pVValue->push_back ((ULong)value);
					}
					else
					{
						ULong& c = (*_pVValue)[index];
						c = (ULong)value;
					}
				}
			}
		}

		//////////////////////////////////////////////////////////////////////////////////////////
		// UInt64erface functions for cell vectors 
	public:
		property Generic::ICell<UInt64>^ CItem[int] 
		{
			virtual Generic::ICell<UInt64>^ get (int index) = INativeVector<Generic::ICell<UInt64>^>::default::get
			{
				return CellBuilder::Instance->Create<UInt64> (default[index]);
			}

			virtual void set (int index, Generic::ICell<UInt64>^ value) = INativeVector<Generic::ICell<UInt64>^>::default::set
			{
				default[index] = (ULong)value->Value;
			}
		}
	public:
		std::vector<ULong>& GetReference ()
		{
			 return *_pVValue;
		}

		static operator std::vector<ULong>& (CULongVector^ a)
		{
			return a->GetReference();
		}
	public:
		virtual bool PrepareFeature (NativeFeature feature)
		{
			switch (feature)
			{
				case NativeFeature::Value :
					if (_pVValue == NULL)
					{
						_pVValue = new std::vector<ULong> ();
						return true;
					}
					break;
			}
			return false;
		}
	};
	ref class CULongMatrix : public System::MarshalByRefObject,  
								public INativeMatrix<UInt64>,
							    public INativeMatrix<Generic::ICell<UInt64>^>
	{
	private:
		std::vector<std::vector<ULong>>* _pVValue;
		Object^ _owner;
	public:
		CULongMatrix ()
		{
			_pVValue = NULL;
		}
		CULongMatrix (std::vector<std::vector<ULong>>& rValue, Object^ owner)
		{
			_pVValue = &rValue;
			_owner = owner;
		}
		CULongMatrix (std::vector<std::vector<ULong>> rValue)
		{
			_pVValue = new std::vector<std::vector<ULong>> (rValue);
		}
		virtual ~CULongMatrix ()
		{
			if (_pVValue != NULL) delete _pVValue;
		}
		property int Count 
		{
			virtual int get ()
			{
				if (_pVValue != NULL) 
				{
					return _pVValue->size();
				}
				return 0;		// should never happen
			}
		}

		property UInt64 default[int, int] 
		{
			virtual UInt64 get (int x, int y) = INativeMatrix<UInt64>::default::get
			{
				if (_pVValue == NULL) throw gcnew NullVectorException ();
				if ((size_t)x >= _pVValue->size() || (size_t)y >= (*_pVValue)[x].size()) throw gcnew RangeException ();

				ULong& native = (*_pVValue)[x][y];
				return (UInt64)native;
			}
			virtual void set (int x, int y, UInt64 value) = INativeMatrix<UInt64>::default::set
			{
				if (_pVValue != NULL)
				{
					if (_pVValue->size() <= (size_t)x)
					{
						// can't happen because vectors are filled from List<> sequentially
						if (_pVValue->size()-1 < (size_t)x) throw gcnew RangeException ();

						_pVValue->push_back (std::vector<ULong>());
					}
					if ((*_pVValue)[x].size() <= (size_t)y)
					{
						if ((*_pVValue)[x].size() < (size_t)y) throw gcnew RangeException ();

						(*_pVValue)[x].push_back ((ULong)value);
					}
					ULong& c = (*_pVValue)[x][y];
					c = (ULong)value;
				}
			}
		}

		property Generic::ICell<UInt64>^ CItem[int, int] 
		{
			virtual Generic::ICell<UInt64>^ get (int x, int y) = INativeMatrix<Generic::ICell<UInt64>^>::default::get
			{
				return CellBuilder::Instance->Create<UInt64> (default[x,y]);
			}
			virtual void set (int x, int y, Generic::ICell<UInt64>^ value) = INativeMatrix<Generic::ICell<UInt64>^>::default::set
			{
				default[x,y] = value->Value;
			}
		}

	public:
		std::vector<std::vector<ULong>>& GetReference ()
		{
			 return *_pVValue;
		}

		static operator std::vector<std::vector<ULong>>& (CULongMatrix^ a)
		{
			return a->GetReference();
		}
	public:
		virtual bool PrepareFeature (NativeFeature feature)
		{
			switch (feature)
			{
				case NativeFeature::Value :
					if (_pVValue == NULL)
					{
						_pVValue = new std::vector<std::vector<ULong>> ();
						return true;
					}
					break;
			}
			return false;
		}
	public:
		virtual INativeVector<UInt64>^ CreateVector () = INativeMatrix<UInt64>::CreateVector
		{
			return gcnew CULongVector ();
		}
	public:
		virtual INativeVector<Generic::ICell<UInt64>^>^ CreateCellVector () = INativeMatrix<Generic::ICell<UInt64>^>::CreateVector
		{
			return gcnew CULongVector ();
		}
	};

	ref class CULongCube : public System::MarshalByRefObject,  
							  public INativeCube<UInt64>,
							  public INativeCube<Generic::ICell<UInt64>^>
	{
	private:
		std::vector<std::vector<std::vector<ULong>>>* _pVValue;
		Object^ _owner;
	public:
		CULongCube ()
		{
			_pVValue = NULL;
		}
		CULongCube (std::vector<std::vector<std::vector<ULong>>>& rValue, Object^ owner)
		{
			_pVValue = &rValue;
			_owner = owner;
		}
		CULongCube (std::vector<std::vector<std::vector<ULong>>> rValue)
		{
			_pVValue = new std::vector<std::vector<std::vector<ULong>>> (rValue);
		}
		virtual ~CULongCube ()
		{
			if (_pVValue != NULL) delete _pVValue;
		}
		property int Count 
		{
			virtual int get ()
			{
				if (_pVValue != NULL) 
				{
					return _pVValue->size();
				}
				return 0;		// should never happen
			}
		}

		property UInt64 default[int, int, int] 
		{
			virtual UInt64 get (int x, int y, int z) = INativeCube<UInt64>::default::get
			{
				if (_pVValue == NULL) throw gcnew NullVectorException ();
				if ((size_t)x >= _pVValue->size() || (size_t)y >= (*_pVValue)[x].size() || (size_t)z >= (*_pVValue)[x][y].size()) throw gcnew RangeException ();

				ULong& native = (*_pVValue)[x][y][z];
				return (UInt64)native;
			}
			virtual void set (int x, int y, int z, UInt64 value) = INativeCube<UInt64>::default::set
			{
				if (_pVValue != NULL)
				{
					if (_pVValue->size() <= (size_t)x)
					{
						// can't happen because vectors are filled from List<> sequentially
						if (_pVValue->size()-1 < (size_t)x) throw gcnew RangeException ();

						_pVValue->push_back (std::vector<std::vector<ULong>>());
					}
					if ((*_pVValue)[x].size() <= (size_t)y)
					{
						if ((*_pVValue)[x].size() < (size_t)y) throw gcnew RangeException ();

						(*_pVValue)[x].push_back (std::vector<ULong> ());
					}
					if ((*_pVValue)[x][y].size() <= (size_t)z)
					{
						if ((*_pVValue)[x][y].size() < (size_t)z) throw gcnew RangeException ();

						(*_pVValue)[x][y].push_back ((ULong)value);
					}
					ULong& c = (*_pVValue)[x][y][z];
					c = (ULong)value;
				}
			}
		}

		property Generic::ICell<UInt64>^ CItem[int, int, int] 
		{
			virtual Generic::ICell<UInt64>^ get (int x, int y, int z) = INativeCube<Generic::ICell<UInt64>^>::default::get
			{
				return CellBuilder::Instance->Create<UInt64> (default[x,y,z]);
			}
			virtual void set (int x, int y, int z, Generic::ICell<UInt64>^ value) = INativeCube<Generic::ICell<UInt64>^>::default::set
			{
				default[x,y,z] = value->Value;
			}
		}

	public:
		std::vector<std::vector<std::vector<ULong>>>& GetReference ()
		{
			 return *_pVValue;
		}

		static operator std::vector<std::vector<std::vector<ULong>>>& (CULongCube^ a)
		{
			return a->GetReference();
		}
	public:
		virtual bool PrepareFeature (NativeFeature feature)
		{
			switch (feature)
			{
				case NativeFeature::Value :
					if (_pVValue == NULL)
					{
						_pVValue = new std::vector<std::vector<std::vector<ULong>>> ();
						return true;
					}
					break;
			}
			return false;
		}
	public:
		virtual INativeMatrix<UInt64>^ CreateMatrix () = INativeCube<UInt64>::CreateMatrix
		{
			return gcnew CULongMatrix ();
		}
	public:
		virtual INativeMatrix<Generic::ICell<UInt64>^>^ CreateCellMatrix () = INativeCube<Generic::ICell<UInt64>^>::CreateMatrix
		{
			return gcnew CULongMatrix ();
		}
	};
	typedef CULongVector CUInt64Vector;
	typedef CULongMatrix CUInt64Matrix;
	typedef CULongCube CUInt64Cube;

	ref class CDateTimeVector : public System::MarshalByRefObject,  
							    public INativeVector<DateTime>,
							    public INativeVector<Generic::ICell<DateTime>^>
	{
	private:
		std::vector<QuantLib::Date>* _pVValue;
		Object^ _owner;
	public:
		CDateTimeVector ()
		{
			_pVValue = NULL;
		}
		CDateTimeVector (std::vector<QuantLib::Date>& rValue, Object^ owner)
		{
			_pVValue = &rValue;
			_owner = owner;
		}
		CDateTimeVector (std::vector<QuantLib::Date> rValue)
		{
			_pVValue = new std::vector<QuantLib::Date> (rValue);
		}
		virtual ~CDateTimeVector ()
		{
			if (_pVValue != NULL) delete _pVValue;
		}

		property int Count 
		{
			virtual int get ()
			{
				if (_pVValue != NULL) 
				{
					return _pVValue->size();
				}
				return 0;		// should never happen
			}
		}

		property DateTime default[int] 
		{
			virtual DateTime get (int index) = INativeVector<DateTime>::default::get
			{
				if (_pVValue == NULL) throw gcnew NullVectorException ();
				if ((size_t)index >= _pVValue->size()) throw gcnew RangeException ();

				DateTime native = ValueHelper::Convert((*_pVValue)[index]);
				return native;
			}
			virtual void set (int index, DateTime value) = INativeVector<DateTime>::default::set
			{
				if (_pVValue != NULL)
				{
					if (_pVValue->size() <= (size_t)index)
					{
						// can't happen because vectors are filled from List<> sequentially
						if (_pVValue->size() < (size_t)index)
						{
							throw gcnew RangeException ();
						}
						_pVValue->push_back (ValueHelper::Convert(value));
					}
					else
					{
						QuantLib::Date& c = (*_pVValue)[index];
						c = ValueHelper::Convert(value);
					}
				}
			}
		}

		//////////////////////////////////////////////////////////////////////////////////////////
		// Interface functions for cell vectors 
	public:
		property Generic::ICell<DateTime>^ CItem[int] 
		{
			virtual Generic::ICell<DateTime>^ get (int index) = INativeVector<Generic::ICell<DateTime>^>::default::get
			{
				return CellBuilder::Instance->Create<DateTime> (default[index]);
			}

			virtual void set (int index, Generic::ICell<DateTime>^ value) = INativeVector<Generic::ICell<DateTime>^>::default::set
			{
				default[index] = value->Value;
			}
		}
	public:
		std::vector<QuantLib::Date>& GetReference ()
		{
			 return *_pVValue;
		}

		static operator std::vector<QuantLib::Date>& (CDateTimeVector^ a)
		{
			return a->GetReference();
		}
	public:
		virtual bool PrepareFeature (NativeFeature feature)
		{
			switch (feature)
			{
				case NativeFeature::Value :
					if (_pVValue == NULL)
					{
						_pVValue = new std::vector<QuantLib::Date> ();
						return true;
					}
					break;
			}
			return false;
		}
	};
	ref class CDateTimeMatrix : public System::MarshalByRefObject,  
								public INativeMatrix<DateTime>,
							    public INativeMatrix<Generic::ICell<DateTime>^>
	{
	private:
		std::vector<std::vector<QuantLib::Date>>* _pVValue;
		Object^ _owner;
	public:
		CDateTimeMatrix ()
		{
			_pVValue = NULL;
		}
		CDateTimeMatrix (std::vector<std::vector<QuantLib::Date>>& rValue, Object^ owner)
		{
			_pVValue = &rValue;
			_owner = owner;
		}
		CDateTimeMatrix (std::vector<std::vector<QuantLib::Date>> rValue)
		{
			_pVValue = new std::vector<std::vector<QuantLib::Date>> (rValue);
		}
		virtual ~CDateTimeMatrix ()
		{
			if (_pVValue != NULL) delete _pVValue;
		}
		property int Count 
		{
			virtual int get ()
			{
				if (_pVValue != NULL) 
				{
					return _pVValue->size();
				}
				return 0;		// should never happen
			}
		}

		property DateTime default[int, int] 
		{
			virtual DateTime get (int x, int y) = INativeMatrix<DateTime>::default::get
			{
				if (_pVValue == NULL) throw gcnew NullVectorException ();
				if ((size_t)x >= _pVValue->size() || (size_t)y >= (*_pVValue)[x].size()) throw gcnew RangeException ();

				QuantLib::Date& native = (*_pVValue)[x][y];
				return ValueHelper::Convert(native);
			}
			virtual void set (int x, int y, DateTime value) = INativeMatrix<DateTime>::default::set
			{
				if (_pVValue != NULL)
				{
					if (_pVValue->size() <= (size_t)x)
					{
						// can't happen because vectors are filled from List<> sequentially
						if (_pVValue->size()-1 < (size_t)x) throw gcnew RangeException ();

						_pVValue->push_back (std::vector<QuantLib::Date>());
					}
					if ((*_pVValue)[x].size() <= (size_t)y)
					{
						if ((*_pVValue)[x].size() < (size_t)y) throw gcnew RangeException ();

						(*_pVValue)[x].push_back (ValueHelper::Convert(value));
					}
					QuantLib::Date& c = (*_pVValue)[x][y];
					c = ValueHelper::Convert(value);
				}
			}
		}

		property Generic::ICell<DateTime>^ CItem[int, int] 
		{
			virtual Generic::ICell<DateTime>^ get (int x, int y) = INativeMatrix<Generic::ICell<DateTime>^>::default::get
			{
				return CellBuilder::Instance->Create<DateTime> (default[x,y]);
			}
			virtual void set (int x, int y, Generic::ICell<DateTime>^ value) = INativeMatrix<Generic::ICell<DateTime>^>::default::set
			{
				default[x,y] = value->Value;
			}
		}

	public:
		std::vector<std::vector<QuantLib::Date>>& GetReference ()
		{
			 return *_pVValue;
		}

		static operator std::vector<std::vector<QuantLib::Date>>& (CDateTimeMatrix^ a)
		{
			return a->GetReference();
		}
	public:
		virtual bool PrepareFeature (NativeFeature feature)
		{
			switch (feature)
			{
				case NativeFeature::Value :
					if (_pVValue == NULL)
					{
						_pVValue = new std::vector<std::vector<QuantLib::Date>> ();
						return true;
					}
					break;
			}
			return false;
		}
	public:
		virtual INativeVector<DateTime>^ CreateVector () = INativeMatrix<DateTime>::CreateVector
		{
			return gcnew CDateTimeVector ();
		}
	public:
		virtual INativeVector<Generic::ICell<DateTime>^>^ CreateCellVector () = INativeMatrix<Generic::ICell<DateTime>^>::CreateVector
		{
			return gcnew CDateTimeVector ();
		}
	};

	ref class CDateTimeCube : public System::MarshalByRefObject,  
							  public INativeCube<DateTime>,
							  public INativeCube<Generic::ICell<DateTime>^>
	{
	private:
		std::vector<std::vector<std::vector<QuantLib::Date>>>* _pVValue;
		Object^ _owner;
	public:
		CDateTimeCube ()
		{
			_pVValue = NULL;
		}
		CDateTimeCube (std::vector<std::vector<std::vector<QuantLib::Date>>>& rValue, Object^ owner)
		{
			_pVValue = &rValue;
			_owner = owner;
		}
		CDateTimeCube (std::vector<std::vector<std::vector<QuantLib::Date>>> rValue)
		{
			_pVValue = new std::vector<std::vector<std::vector<QuantLib::Date>>> (rValue);
		}
		virtual ~CDateTimeCube ()
		{
			if (_pVValue != NULL) delete _pVValue;
		}
		property int Count 
		{
			virtual int get ()
			{
				if (_pVValue != NULL) 
				{
					return _pVValue->size();
				}
				return 0;		// should never happen
			}
		}

		property DateTime default[int, int, int] 
		{
			virtual DateTime get (int x, int y, int z) = INativeCube<DateTime>::default::get
			{
				if (_pVValue == NULL) throw gcnew NullVectorException ();
				if ((size_t)x >= _pVValue->size() || (size_t)y >= (*_pVValue)[x].size() || (size_t)z >= (*_pVValue)[x][y].size()) throw gcnew RangeException ();

				DateTime native = ValueHelper::Convert((*_pVValue)[x][y][z]);
				return native;
			}
			virtual void set (int x, int y, int z, DateTime value) = INativeCube<DateTime>::default::set
			{
				if (_pVValue != NULL)
				{
					if (_pVValue->size() <= (size_t)x)
					{
						// can't happen because vectors are filled from List<> sequentially
						if (_pVValue->size()-1 < (size_t)x) throw gcnew RangeException ();

						_pVValue->push_back (std::vector<std::vector<QuantLib::Date>>());
					}
					if ((*_pVValue)[x].size() <= (size_t)y)
					{
						if ((*_pVValue)[x].size() < (size_t)y) throw gcnew RangeException ();

						(*_pVValue)[x].push_back (std::vector<QuantLib::Date> ());
					}
					if ((*_pVValue)[x][y].size() <= (size_t)z)
					{
						if ((*_pVValue)[x][y].size() < (size_t)z) throw gcnew RangeException ();

						(*_pVValue)[x][y].push_back (ValueHelper::Convert(value));
					}
					QuantLib::Date& c = (*_pVValue)[x][y][z];
					c = ValueHelper::Convert(value);
				}
			}
		}

		property Generic::ICell<DateTime>^ CItem[int, int, int] 
		{
			virtual Generic::ICell<DateTime>^ get (int x, int y, int z) = INativeCube<Generic::ICell<DateTime>^>::default::get
			{
				return CellBuilder::Instance->Create<DateTime> (default[x,y,z]);
			}
			virtual void set (int x, int y, int z, Generic::ICell<DateTime>^ value) = INativeCube<Generic::ICell<DateTime>^>::default::set
			{
				default[x,y,z] = value->Value;
			}
		}

	public:
		std::vector<std::vector<std::vector<QuantLib::Date>>>& GetReference ()
		{
			 return *_pVValue;
		}

		static operator std::vector<std::vector<std::vector<QuantLib::Date>>>& (CDateTimeCube^ a)
		{
			return a->GetReference();
		}
	public:
		virtual bool PrepareFeature (NativeFeature feature)
		{
			switch (feature)
			{
				case NativeFeature::Value :
					if (_pVValue == NULL)
					{
						_pVValue = new std::vector<std::vector<std::vector<QuantLib::Date>>> ();
						return true;
					}
					break;
			}
			return false;
		}
	public:
		virtual INativeMatrix<DateTime>^ CreateMatrix () = INativeCube<DateTime>::CreateMatrix
		{
			return gcnew CDateTimeMatrix ();
		}
	public:
		virtual INativeMatrix<Generic::ICell<DateTime>^>^ CreateCellMatrix () = INativeCube<Generic::ICell<DateTime>^>::CreateMatrix
		{
			return gcnew CDateTimeMatrix ();
		}
	};
	ref class CStringVector : public System::MarshalByRefObject,  
							    public INativeVector<String^>,
							    public INativeVector<Generic::ICell<String^>^>
	{
	private:
		std::vector<std::string>* _pVValue;
		Object^ _owner;

	public:
		CStringVector ()
		{
			_pVValue = NULL;
		}
		CStringVector (std::vector<std::string>& rValue, Object^ owner)
		{
			_pVValue = &rValue;
			_owner = owner;
		}
		CStringVector (std::vector<std::string> rValue)
		{
			_pVValue = new std::vector<std::string> (rValue);
		}
		virtual ~CStringVector ()
		{
			if (_pVValue != NULL) delete _pVValue;
		}

		property int Count 
		{
			virtual int get ()
			{
				if (_pVValue != NULL) 
				{
					return _pVValue->size();
				}
				return 0;		// should never happen
			}
		}

		property String^ default[int] 
		{
			virtual String^ get (int index) = INativeVector<String^>::default::get
			{
				if (_pVValue == NULL) throw gcnew NullVectorException ();
				if ((size_t)index >= _pVValue->size()) throw gcnew RangeException ();

				String^ native = ValueHelper::Convert((*_pVValue)[index]);
				return native;
			}
			virtual void set (int index, String^ value) = INativeVector<String^>::default::set
			{
				if (_pVValue != NULL)
				{
					if (_pVValue->size() <= (size_t)index)
					{
						// can't happen because vectors are filled from List<> sequentially
						if (_pVValue->size() < (size_t)index)
						{
							throw gcnew RangeException ();
						}
						_pVValue->push_back (ValueHelper::Convert(value));
					}
					else
					{
						std::string& c = (*_pVValue)[index];
						c = ValueHelper::Convert (value);
					}
				}
			}
		}

		//////////////////////////////////////////////////////////////////////////////////////////
		// Interface functions for cell vectors 
	public:
		property Generic::ICell<String^>^ CItem[int] 
		{
			virtual Generic::ICell<String^>^ get (int index) = INativeVector<Generic::ICell<String^>^>::default::get
			{
				return CellBuilder::Instance->Create<String^> (default[index]);
			}

			virtual void set (int index, Generic::ICell<String^>^ value) = INativeVector<Generic::ICell<String^>^>::default::set
			{
				default[index] = value->Value;
			}
		}
	public:
		std::vector<std::string>& GetReference ()
		{
			 return *_pVValue;
		}

		static operator std::vector<std::string>& (CStringVector^ a)
		{
			return a->GetReference();
		}
	public:
		virtual bool PrepareFeature (NativeFeature feature)
		{
			switch (feature)
			{
				case NativeFeature::Value :
					if (_pVValue == NULL)
					{
						_pVValue = new std::vector<std::string> ();
						return true;
					}
					break;
			}
			return false;
		}
	};
	ref class CStringMatrix : public System::MarshalByRefObject,  
								public INativeMatrix<String^>,
							    public INativeMatrix<Generic::ICell<String^>^>
	{
	private:
		std::vector<std::vector<std::string>>* _pVValue;
		Object^ _owner;
	public:
		CStringMatrix ()
		{
			_pVValue = NULL;
		}
		CStringMatrix (std::vector<std::vector<std::string>>& rValue, Object^ owner)
		{
			_pVValue = &rValue;
			_owner = owner;
		}
		CStringMatrix (std::vector<std::vector<std::string>> rValue)
		{
			_pVValue = new std::vector<std::vector<std::string>> (rValue);
		}
		virtual ~CStringMatrix ()
		{
			if (_pVValue != NULL) delete _pVValue;
		}
		property int Count 
		{
			virtual int get ()
			{
				if (_pVValue != NULL) 
				{
					return _pVValue->size();
				}
				return 0;		// should never happen
			}
		}

		property String^ default[int, int] 
		{
			virtual String^ get (int x, int y) = INativeMatrix<String^>::default::get
			{
				if (_pVValue == NULL) throw gcnew NullVectorException ();
				if ((size_t)x >= _pVValue->size() || (size_t)y >= (*_pVValue)[x].size()) throw gcnew RangeException ();

				String^ native = ValueHelper::Convert((*_pVValue)[x][y]);
				return native;
			}
			virtual void set (int x, int y, String^ value) = INativeMatrix<String^>::default::set
			{
				if (_pVValue != NULL)
				{
					if (_pVValue->size() <= (size_t)x)
					{
						// can't happen because vectors are filled from List<> sequentially
						if (_pVValue->size()-1 < (size_t)x) throw gcnew RangeException ();

						_pVValue->push_back (std::vector<std::string>());
					}
					if ((*_pVValue)[x].size() <= (size_t)y)
					{
						if ((*_pVValue)[x].size() < (size_t)y) throw gcnew RangeException ();

						(*_pVValue)[x].push_back (ValueHelper::Convert(value));
					}
					std::string& c = (*_pVValue)[x][y];
					c = ValueHelper::Convert(value);
				}
			}
		}

		property Generic::ICell<String^>^ CItem[int, int] 
		{
			virtual Generic::ICell<String^>^ get (int x, int y) = INativeMatrix<Generic::ICell<String^>^>::default::get
			{
				return CellBuilder::Instance->Create<String^> (default[x,y]);
			}
			virtual void set (int x, int y, Generic::ICell<String^>^ value) = INativeMatrix<Generic::ICell<String^>^>::default::set
			{
				default[x,y] = value->Value;
			}
		}

	public:
		std::vector<std::vector<std::string>>& GetReference ()
		{
			 return *_pVValue;
		}

		static operator std::vector<std::vector<std::string>>& (CStringMatrix^ a)
		{
			return a->GetReference();
		}
	public:
		virtual bool PrepareFeature (NativeFeature feature)
		{
			switch (feature)
			{
				case NativeFeature::Value :
					if (_pVValue == NULL)
					{
						_pVValue = new std::vector<std::vector<std::string>> ();
						return true;
					}
					break;
			}
			return false;
		}
	public:
		virtual INativeVector<String^>^ CreateVector () = INativeMatrix<String^>::CreateVector
		{
			return gcnew CStringVector ();
		}
	public:
		virtual INativeVector<Generic::ICell<String^>^>^ CreateCellVector () = INativeMatrix<Generic::ICell<String^>^>::CreateVector
		{
			return gcnew CStringVector ();
		}
	};

	ref class CStringCube : public System::MarshalByRefObject,  
							  public INativeCube<String^>,
							  public INativeCube<Generic::ICell<String^>^>
	{
	private:
		std::vector<std::vector<std::vector<std::string>>>* _pVValue;
		Object^ _owner;
	public:
		CStringCube ()
		{
			_pVValue = NULL;
		}
		CStringCube (std::vector<std::vector<std::vector<std::string>>>& rValue, Object^ owner)
		{
			_pVValue = &rValue;
			_owner = owner;
		}
		CStringCube (std::vector<std::vector<std::vector<std::string>>> rValue)
		{
			_pVValue = new std::vector<std::vector<std::vector<std::string>>> (rValue);
		}
		virtual ~CStringCube ()
		{
			if (_pVValue != NULL) delete _pVValue;
		}
		property int Count 
		{
			virtual int get ()
			{
				if (_pVValue != NULL) 
				{
					return _pVValue->size();
				}
				return 0;		// should never happen
			}
		}

		property String^ default[int, int, int] 
		{
			virtual String^ get (int x, int y, int z) = INativeCube<String^>::default::get
			{
				if (_pVValue == NULL) throw gcnew NullVectorException ();
				if ((size_t)x >= _pVValue->size() || (size_t)y >= (*_pVValue)[x].size() || (size_t)z >= (*_pVValue)[x][y].size()) throw gcnew RangeException ();

				String^ native = ValueHelper::Convert((*_pVValue)[x][y][z]);
				return native;
			}
			virtual void set (int x, int y, int z, String^ value) = INativeCube<String^>::default::set
			{
				if (_pVValue != NULL)
				{
					if (_pVValue->size() <= (size_t)x)
					{
						// can't happen because vectors are filled from List<> sequentially
						if (_pVValue->size()-1 < (size_t)x) throw gcnew RangeException ();

						_pVValue->push_back (std::vector<std::vector<std::string>>());
					}
					if ((*_pVValue)[x].size() <= (size_t)y)
					{
						if ((*_pVValue)[x].size() < (size_t)y) throw gcnew RangeException ();

						(*_pVValue)[x].push_back (std::vector<std::string> ());
					}
					if ((*_pVValue)[x][y].size() <= (size_t)z)
					{
						if ((*_pVValue)[x][y].size() < (size_t)z) throw gcnew RangeException ();

						(*_pVValue)[x][y].push_back (ValueHelper::Convert(value));
					}
					std::string& c = (*_pVValue)[x][y][z];
					c = ValueHelper::Convert (value);
				}
			}
		}


		property Generic::ICell<String^>^ CItem[int, int, int] 
		{
			virtual Generic::ICell<String^>^ get (int x, int y, int z) = INativeCube<Generic::ICell<String^>^>::default::get
			{
				return CellBuilder::Instance->Create<String^> (default[x,y,z]);
			}
			virtual void set (int x, int y, int z, Generic::ICell<String^>^ value) = INativeCube<Generic::ICell<String^>^>::default::set
			{
				default[x,y,z] = value->Value;
			}
		}

	public:
		std::vector<std::vector<std::vector<std::string>>>& GetReference ()
		{
			 return *_pVValue;
		}

		static operator std::vector<std::vector<std::vector<std::string>>>& (CStringCube^ a)
		{
			return a->GetReference();
		}
	public:
		virtual bool PrepareFeature (NativeFeature feature)
		{
			switch (feature)
			{
				case NativeFeature::Value :
					if (_pVValue == NULL)
					{
						_pVValue = new std::vector<std::vector<std::vector<std::string>>> ();
						return true;
					}
					break;
			}
			return false;
		}
	public:
		virtual INativeMatrix<String^>^ CreateMatrix () = INativeCube<String^>::CreateMatrix
		{
			return gcnew CStringMatrix ();
		}
	public:
		virtual INativeMatrix<Generic::ICell<String^>^>^ CreateCellMatrix () = INativeCube<Generic::ICell<String^>^>::CreateMatrix
		{
			return gcnew CStringMatrix ();
		}
	};
	ref class CBooleanVector : public System::MarshalByRefObject,  
							    public INativeVector<Boolean>,
							    public INativeVector<Generic::ICell<Boolean>^>
	{
	private:
		std::vector<bool>* _pVValue;
		Object^ _owner;

	public:
		CBooleanVector ()
		{
			_pVValue = NULL;
		}
		CBooleanVector (std::vector<bool>& rValue, Object^ owner)
		{
			_pVValue = &rValue;
			_owner = owner;
		}
		CBooleanVector (std::vector<bool> rValue)
		{
			_pVValue = new std::vector<bool> (rValue);
		}
		virtual ~CBooleanVector ()
		{
			if (_pVValue != NULL) delete _pVValue;
		}

		property int Count 
		{
			virtual int get ()
			{
				if (_pVValue != NULL) 
				{
					return _pVValue->size();
				}
				return 0;		// should never happen
			}
		}

		property Boolean default[int] 
		{
			virtual Boolean get (int index) = INativeVector<Boolean>::default::get
			{
				if (_pVValue == NULL) throw gcnew NullVectorException ();
				if ((size_t)index >= _pVValue->size()) throw gcnew RangeException ();

				Boolean native = (*_pVValue)[index];
				return native;
			}
			virtual void set (int index, Boolean value) = INativeVector<Boolean>::default::set
			{
				if (_pVValue != NULL)
				{
					if (_pVValue->size() <= (size_t)index)
					{
						// can't happen because vectors are filled from List<> sequentially
						if (_pVValue->size() < (size_t)index)
						{
							throw gcnew RangeException ();
						}
						_pVValue->push_back (value);
					}
					else
					{
						(*_pVValue)[index] = value;
					}
				}
			}
		}

		//////////////////////////////////////////////////////////////////////////////////////////
		// Interface functions for cell vectors 
	public:
		property Generic::ICell<Boolean>^ CItem[int] 
		{
			virtual Generic::ICell<Boolean>^ get (int index) = INativeVector<Generic::ICell<Boolean>^>::default::get
			{
				return CellBuilder::Instance->Create<Boolean> (default[index]);
			}

			virtual void set (int index, Generic::ICell<Boolean>^ value) = INativeVector<Generic::ICell<Boolean>^>::default::set
			{
				default[index] = value->Value;
			}
		}
	public:
		std::vector<bool>& GetReference ()
		{
			 return *_pVValue;
		}

		static operator std::vector<bool>& (CBooleanVector^ a)
		{
			return a->GetReference();
		}
	public:
		virtual bool PrepareFeature (NativeFeature feature)
		{
			switch (feature)
			{
				case NativeFeature::Value :
					if (_pVValue == NULL)
					{
						_pVValue = new std::vector<bool> ();
						return true;
					}
					break;
			}
			return false;
		}
	};
	ref class CBooleanMatrix : public System::MarshalByRefObject,  
								public INativeMatrix<Boolean>,
							    public INativeMatrix<Generic::ICell<Boolean>^>
	{
	private:
		std::vector<std::vector<bool>>* _pVValue;
		Object^ _owner;
	public:
		CBooleanMatrix ()
		{
			_pVValue = NULL;
		}
		CBooleanMatrix (std::vector<std::vector<bool>>& rValue, Object^ owner)
		{
			_pVValue = &rValue;
			_owner = owner;
		}
		CBooleanMatrix (std::vector<std::vector<bool>> rValue)
		{
			_pVValue = new std::vector<std::vector<bool>> (rValue);
		}
		virtual ~CBooleanMatrix ()
		{
			if (_pVValue != NULL) delete _pVValue;
		}

		property int Count 
		{
			virtual int get ()
			{
				if (_pVValue != NULL) 
				{
					return _pVValue->size();
				}
				return 0;		// should never happen
			}
		}

		property Boolean default[int, int] 
		{
			virtual Boolean get (int x, int y) = INativeMatrix<Boolean>::default::get
			{
				if (_pVValue == NULL) throw gcnew NullVectorException ();
				if ((size_t)x >= _pVValue->size() || (size_t)y >= (*_pVValue)[x].size()) throw gcnew RangeException ();

				return (*_pVValue)[x][y];
			}
			virtual void set (int x, int y, Boolean value) = INativeMatrix<Boolean>::default::set
			{
				if (_pVValue != NULL)
				{
					if (_pVValue->size() <= (size_t)x)
					{
						// can't happen because vectors are filled from List<> sequentially
						if (_pVValue->size()-1 < (size_t)x) throw gcnew RangeException ();

						_pVValue->push_back (std::vector<Boolean>());
					}
					if ((*_pVValue)[x].size() <= (size_t)y)
					{
						if ((*_pVValue)[x].size() < (size_t)y) throw gcnew RangeException ();

						(*_pVValue)[x].push_back (value);
					}
					(*_pVValue)[x][y] = value;
				}
			}
		}

		property Generic::ICell<Boolean>^ CItem[int, int] 
		{
			virtual Generic::ICell<Boolean>^ get (int x, int y) = INativeMatrix<Generic::ICell<Boolean>^>::default::get
			{
				return CellBuilder::Instance->Create<Boolean> (default[x,y]);
			}
			virtual void set (int x, int y, Generic::ICell<Boolean>^ value) = INativeMatrix<Generic::ICell<Boolean>^>::default::set
			{
				default[x,y] = value->Value;
			}
		}

	public:
		std::vector<std::vector<bool>>& GetReference ()
		{
			 return *_pVValue;
		}

		static operator std::vector<std::vector<bool>>& (CBooleanMatrix^ a)
		{
			return a->GetReference();
		}
	public:
		virtual bool PrepareFeature (NativeFeature feature)
		{
			switch (feature)
			{
				case NativeFeature::Value :
					if (_pVValue == NULL)
					{
						_pVValue = new std::vector<std::vector<bool>> ();
						return true;
					}
					break;
			}
			return false;
		}
	public:
		virtual INativeVector<Boolean>^ CreateVector () = INativeMatrix<Boolean>::CreateVector
		{
			return gcnew CBooleanVector ();
		}
	public:
		virtual INativeVector<Generic::ICell<Boolean>^>^ CreateCellVector () = INativeMatrix<Generic::ICell<Boolean>^>::CreateVector
		{
			return gcnew CBooleanVector ();
		}
	};

	ref class CBooleanCube : public System::MarshalByRefObject,  
							  public INativeCube<Boolean>,
							  public INativeCube<Generic::ICell<Boolean>^>
	{
	private:
		std::vector<std::vector<std::vector<bool>>>* _pVValue;
		Object^ _owner;
	public:
		CBooleanCube ()
		{
			_pVValue = NULL;
		}
		CBooleanCube (std::vector<std::vector<std::vector<bool>>>& rValue, Object^ owner)
		{
			_pVValue = &rValue;
			_owner = owner;
		}
		CBooleanCube (std::vector<std::vector<std::vector<bool>>> rValue)
		{
			_pVValue = new std::vector<std::vector<std::vector<bool>>> (rValue);
		}
		virtual ~CBooleanCube ()
		{
			if (_pVValue != NULL) delete _pVValue;
		}
		property int Count 
		{
			virtual int get ()
			{
				if (_pVValue != NULL) 
				{
					return _pVValue->size();
				}
				return 0;		// should never happen
			}
		}

		property Boolean default[int, int, int] 
		{
			virtual Boolean get (int x, int y, int z) = INativeCube<Boolean>::default::get
			{
				if (_pVValue == NULL) throw gcnew NullVectorException ();
				if ((size_t)x >= _pVValue->size() || (size_t)y >= (*_pVValue)[x].size() || (size_t)z >= (*_pVValue)[x][y].size()) throw gcnew RangeException ();

				return (*_pVValue)[x][y][z];
			}
			virtual void set (int x, int y, int z, Boolean value) = INativeCube<Boolean>::default::set
			{
				if (_pVValue != NULL)
				{
					if (_pVValue->size() <= (size_t)x)
					{
						// can't happen because vectors are filled from List<> sequentially
						if (_pVValue->size()-1 < (size_t)x) throw gcnew RangeException ();

						_pVValue->push_back (std::vector<std::vector<Boolean>>());
					}
					if ((*_pVValue)[x].size() <= (size_t)y)
					{
						if ((*_pVValue)[x].size() < (size_t)y) throw gcnew RangeException ();

						(*_pVValue)[x].push_back (std::vector<Boolean> ());
					}
					if ((*_pVValue)[x][y].size() <= (size_t)z)
					{
						if ((*_pVValue)[x][y].size() < (size_t)z) throw gcnew RangeException ();

						(*_pVValue)[x][y].push_back (value);
					}
					(*_pVValue)[x][y][z] = value;
				}
			}
		}

		property Generic::ICell<Boolean>^ CItem[int, int, int] 
		{
			virtual Generic::ICell<Boolean>^ get (int x, int y, int z) = INativeCube<Generic::ICell<Boolean>^>::default::get
			{
				return CellBuilder::Instance->Create<Boolean> (default[x,y,z]);
			}
			virtual void set (int x, int y, int z, Generic::ICell<Boolean>^ value) = INativeCube<Generic::ICell<Boolean>^>::default::set
			{
				default[x,y,z] = value->Value;
			}
		}

	public:
		std::vector<std::vector<std::vector<bool>>>& GetReference ()
		{
			 return *_pVValue;
		}

		static operator std::vector<std::vector<std::vector<bool>>>& (CBooleanCube^ a)
		{
			return a->GetReference();
		}
	public:
		virtual bool PrepareFeature (NativeFeature feature)
		{
			switch (feature)
			{
				case NativeFeature::Value :
					if (_pVValue == NULL)
					{
						_pVValue = new std::vector<std::vector<std::vector<bool>>> ();
						return true;
					}
					break;
			}
			return false;
		}
	public:
		virtual INativeMatrix<Boolean>^ CreateMatrix () = INativeCube<Boolean>::CreateMatrix
		{
			return gcnew CBooleanMatrix ();
		}
	public:
		virtual INativeMatrix<Generic::ICell<Boolean>^>^ CreateCellMatrix () = INativeCube<Generic::ICell<Boolean>^>::CreateMatrix
		{
			return gcnew CBooleanMatrix ();
		}
	};


}
